/**
 * 
 */
package biz.innovasoft.ndb;

import java.io.Serializable;
import java.lang.reflect.Field;
import java.util.Collection;

import biz.innovasoft.ndb.annotations.OID;

/**
 * 
 * @author Diego Miranda
 *
 */
public class StoreHelper implements Serializable {

	private static final long serialVersionUID = 1636317280646847592L;

	private GenericRepository repository;
	
	public StoreHelper (GenericRepository repository) {
		this.repository = repository;
	}
	
	public Object store(Object object) throws RepositoryException {
		return this.store(object, true);
	}

	public Long store(Object object, boolean index)
			throws RepositoryException {
				
		Long oid = repository.objectId;
		boolean fromStack = false;
		synchronized (repository.availableOids) {
			if (repository.availableOids.size() > 0) {
				oid = repository.availableOids.pop();
				fromStack = true;
			}
		}
		
		repository.getObjects().put(oid, object);
		
		if (index) {
			try {
				repository.indexObject(oid, object);
			} catch (RepositoryException e) {
				if (fromStack) repository.availableOids.push(oid);
				throw e;
			}
		}
		
		if (!fromStack) repository.objectId++;
		
		return oid;
		
	}

	public Long[] store(Collection<?> objects, boolean index)
			throws RepositoryException {
		int idx = 0;
		Long []ids = new Long[objects.size()];
		for (Object object : objects) {
			ids[idx++] = store(object, index); 
		}
		return ids;
	}

	@SuppressWarnings("unused")
	private void putOidInObject(Object object, Object oid) {
		Class<?> cls = object.getClass();
		Field[] fields = cls.getFields();
		for (Field field : fields) {
			if (field.isAnnotationPresent(OID.class)) {
				field.setAccessible(true);
				try {
					field.set(object, oid);
				} catch (Exception e) {
					e.printStackTrace();
				}
				break;
			}
		}
	}

}
